#include "IR_InfraredReceive.h"
#include <avr/interrupt.h>

IR_InfraredReceive::IR_InfraredReceive(void)
{
	//ROBO3_MioBoard::init();
}
IR_InfraredReceive::IR_InfraredReceive(uint8_t pin)
{
	_port = 0;
	_irPin = pin;
	pinMode(_irPin,INPUT);
	IR_InfraredReceive::init();
}

void IR_InfraredReceive::setpin(uint8_t pin)
{
	_port = 0;
	_irPin = pin;
	pinMode(_irPin,INPUT);
	IR_InfraredReceive::init();
}

void IR_InfraredReceive::pin2PCMSK(uint8_t pin)
{
	if((pin>=0)&&(pin<=7))
	{
		PCMSK0 = 0;
		PCMSK1 = 0;
		PCMSK2 = 0x01<<pin;
	}
	if((pin>=8)&&(pin<=13))
	{
		PCMSK0 = 0x01<<(pin-8);
		PCMSK1 = 0;
		PCMSK2 = 0;
	}
	if(pin==A0)
	{
		PCMSK0 = 0;
		PCMSK1 = 0x01;
		PCMSK2 = 0;
	}	
	if(pin==A1)
	{
		PCMSK0 = 0;
		PCMSK1 = 0x02;
		PCMSK2 = 0;
	}
	if(pin==A2)
	{
		PCMSK0 = 0;
		PCMSK1 = 0x04;
		PCMSK2 = 0;
	}
	if(pin==A3)
	{
		PCMSK0 = 0;
		PCMSK1 = 0x08;
		PCMSK2 = 0;
	}
	if(pin==A4)
	{
		PCMSK0 = 0;
		PCMSK1 = 0x10;
		PCMSK2 = 0;
	}
	if(pin==A5)
	{
		PCMSK0 = 0;
		PCMSK1 = 0x20;
		PCMSK2 = 0;
	}
}


void IR_InfraredReceive::init(void)
{
		irReceiveTime = 0;
		cli();
		PCICR = 0x07;//PCIE0,PCIE1,PCIE2 enable		
		IR_InfraredReceive::pin2PCMSK(_irPin);//PCINTx enable
		sei();
		irDataIndex = 0;
		newPackage = 0;
		irData = 0;
		irDataOld = 0;
		irReceiveTime = 0; 
		dataTimeNew = 0;
		dataTimeOld = 0;
}

void IR_InfraredReceive::dataUpdate(void)
{
		dataTimeNew = micros()-irReceiveTime;
		irReceiveTime = micros();
		delayMicroseconds(5);
		uint8_t irVol = digitalRead(_irPin);

		if(match(dataTimeNew,4500)&&match(dataTimeOld,9000)&&(irVol == LOW))//单按键的头码
		{
			irDataIndex = 0;
			newPackage = 1;
			irData = 0;//32位 红外线遥控器数据
			dataTimeNew = 0;
			dataTimeOld = 0;
			//Serial.println(1);
		}
		else if(match(dataTimeNew,2250)&&match(dataTimeOld,9000)&&(irVol == LOW))//连续按键的头码
		//else if(match(dataTimeNew,2500)&&match(dataTimeOld,9000)&&(irVol == LOW))//连续按键的头码
		{
			irDataIndex = 0;
			newPackage = 1;
			irData = irDataOld;//32位 红外线遥控器数据
			dataTimeNew = 0;
			dataTimeOld = 0;
			//Serial.println(2);
		}
		else if(match(dataTimeNew,560)&&match(dataTimeOld,560)&&(irVol == LOW)&&(newPackage == 1))//数据0
		{
			//irData |= (uint32_t)(0<<irDataIndex);
			irDataIndex++;
			dataTimeNew = 0;
			dataTimeOld = 0;
			//Serial.println(2);
		}
		else if(match(dataTimeNew,1680)&&match(dataTimeOld,560)&&(irVol == LOW)&&(newPackage == 1))//数据1
		{
			irData |= (uint32_t)1<<irDataIndex;
			irDataIndex++;
			dataTimeNew = 0;
			dataTimeOld = 0;
			//Serial.println(3);
		}
		else if(match(dataTimeNew,40180)&&match(dataTimeOld,560)&&(irVol == LOW)&&(newPackage == 1))//单键的结束码
		//else if(match(dataTimeNew,25000)&&match(dataTimeOld,560)&&(irVol == LOW)&&(newPackage == 1))//单键的结束码
		{
			if(irDataIndex != 32)//没有完整的32位数据
				irData = 0;
			else
				irDataOld = irData;
			newPackage = 0;//结束一帧数据
			irDataIndex = 0;
			dataTimeNew = 0;
			dataTimeOld = 0;
			//Serial.println(4);
		}
		else if(match(dataTimeNew,93940)&&match(dataTimeOld,560)&&(irVol == LOW)&&(newPackage == 1))//连续键的结束码
		//else if(match(dataTimeNew,95000)&&match(dataTimeOld,560)&&(irVol == LOW)&&(newPackage == 1))//连续键的结束码
		{
			newPackage = 0;//结束一帧数据
			irDataIndex = 0;
			dataTimeNew = 0;
			dataTimeOld = 0;
			irData = irDataOld;
			//Serial.println(5);
		}
		else
		{
			/*Serial.print(dataTimeNew);
			Serial.print("  ");
			Serial.println(dataTimeOld);*/
		}
		dataTimeOld = dataTimeNew;
}

void IR_InfraredReceive::checkSignal(void)
{
	if(millis() > irDecodeTime + 50)
	{
		irDecodeTime = millis();
		if(_port == 0)
		{
			if((micros() - irReceiveTime) > 200000)
			{
				irData = 0;
				irDataOld = 0;
			}
			/*if((micros() - irReceiveTime) > 800000)
			{
				irData = 0;
				irDataOld = 0;
			}*/
		}
		else
		{
		}
	}
}

uint8_t IR_InfraredReceive::read_u8(void)
{
	return irData>>24;
}
uint32_t IR_InfraredReceive::read_u321(void)
{
	return irData;
}
uint32_t IR_InfraredReceive::read_u32(void)
{
	return irDataOld;
}
uint8_t IR_InfraredReceive::read(void)
{
	switch(read_u8())
	{
		case 186:
			button = BUTTON_SHUT_DOWN;
		break;
		case 185:
			button = BUTTON_MENU;
		break;
		case 184:
			button = BUTTON_SILENCE;
		break;
		case 187:
			button = BUTTON_MODE;
		break;
		case 191:
			button = BUTTON_PLUS;
		break;
		case 188:
			button = BUTTON_RETURN;
		break;
		case 248:
			button = BUTTON_FAST_BACKWARD;
		break;
		case 234:
			button = BUTTON_PLAY_PAUSE;
		break;
		case 246:
			button = BUTTON_FAST_FORWARD;
		break;
		case 233:
			button = BUTTON_ZERO;
		break;
		case 230:
			button = BUTTON_MINUS;
		break;
		case 242:
			button = BUTTON_OK;
		break;
		case 243:
			button = BUTTON_ONE;
		break;
		case 231:
			button = BUTTON_TWO;
		break;
		case 161:
			button = BUTTON_THREE;
		break;
		case 247:
			button = BUTTON_FOUR;
		break;
		case 227:
			button = BUTTON_FIVE;
		break;
		case 165:
			button = BUTTON_SIX;
		break;
		case 189:
			button = BUTTON_SEVEN;
		break;
		case 173:
			button = BUTTON_EIGHT;
		break;
		case 181:
			button = BUTTON_NINE;
		break;
		/********************for  方小方**/
		//case 248:  //右边  //跟上边248 重复
		//break;
		case 249://左
		break;
		case 250://中心
		break;
		case 251://下右
		break;
		case 252://下左
		break;
		case 253://下
		break;
		case 254://上
		break;
		/********************for  方小方**/
		default :
			button = BUTTON_NULL;
		break;
	}
	return button;
}

bool IR_InfraredReceive::match(uint32_t measured_ticks, uint32_t desired_us)
{
	//Serial.print(measured_ticks);Serial.print(",");Serial.println(desired_us);
	return(measured_ticks >= desired_us - (desired_us>>2)-1 && measured_ticks <= desired_us + (desired_us>>2)+1);//判断前后25%的误差
}

